﻿#region Using directives

using System;
using System.Collections.Generic;
using System.Text;

using Weazel.Badger.Vhdl.Expressions;

#endregion

namespace Weazel.Badger.Vhdl.Statements
{
  public class CaseStatement : SequentialStatement, IStatementCollection, IComponent
  {
    private Expression expression;
    public Expression Expression
    {
      get
      {
        return expression;
      }

      set
      {
        expression = value;
      }
    }

    private List<CaseStatementChoice> choices = new List<CaseStatementChoice>();

    private bool doNotIncludeOthersChoice;
    public bool DoNotIncludeOthersChoice
    {
      get
      {
        return doNotIncludeOthersChoice;
      }

      set
      {
        doNotIncludeOthersChoice = value;
      }
    }


    private StatementCollection othersStatements; // = new StatementCollection();
    public StatementCollection OthersStatements
    {
      get
      {
        return othersStatements;
      }

      set
      {
        othersStatements = value;
      }
    }


		public override void Resolve(Entity entity, Process process, StatementCollection statements)
    {
      // resolve statements of each choice ..      
      foreach (CaseStatementChoice c in choices)
				c.Resolve(entity, process, statements);

      // do not forget the "others" choice
			othersStatements.Resolve(entity, process, statements);          
    }

    public override void Verify(ref List<VerifyMessage> messages)
    {
      if (expression == null)
        throw new NullReferenceException();

      expression.VerifyType(ref messages);

      foreach (CaseStatementChoice choice in choices)
        choice.Verify(ref messages);
    }

    public CaseStatement()
    {
      othersStatements = new StatementCollection();
    }

    public void AddChoice(CaseStatementChoice choice)
    {
      choices.Add(choice); 
    }

    public override void Write(System.CodeDom.Compiler.IndentedTextWriter writer)
    {
      writer.WriteLine("case ({0}) is", expression.ToString());
      writer.Indent++;

      foreach (CaseStatementChoice choice in choices)
        choice.Write(writer);

      if (!doNotIncludeOthersChoice)
      {
        writer.WriteLine("when others=>");
        writer.Indent++;

          othersStatements.Write(writer);

        writer.Indent--;
      }

      writer.Indent--;
      writer.WriteLine("end case;");
    }
  }
}
